import * as THREE from "../../../three/build/three.module.js"
import {OrbitControls} from "../../../three/examples/jsm/controls/OrbitControls.js"
import { GLTFLoader } from "../../../three/examples/jsm/loaders/GLTFLoader.js";

let renderer, camera, scene, nextFunctions=[];
let earth, plane, rubbishs, bins;
let selectedRubbish = {rubbish:null, pos:new THREE.Vector3()};

init();
createScene();
animate();
createRay();

window.rubbishs = rubbishs;

function init(){
    scene = new THREE.Scene();
    camera = new THREE.PerspectiveCamera(20, window.innerWidth/ window.innerHeight, 0.01, 1000);
    renderer = new THREE.WebGLRenderer({ antialias: true, logarithmicDepthBuffer: true });

    renderer.setSize(window.innerWidth, window.innerHeight);
    renderer.setClearColor(0x227777);
    document.body.appendChild(renderer.domElement);
    camera.position.z = 20;

    // new OrbitControls(camera,renderer.domElement);

    window.scene = scene;
    window.camera = camera;
    window.renderer = renderer;
}
function animate(){
    requestAnimationFrame(animate);
    next();
    render();
}

function render(){
    renderer.render(scene,camera);
}

function next(){
    for(let i = 0; i<nextFunctions.length; i++){
        nextFunctions[i]();
    }
}

function createScene(){
    let textureLoader = new THREE.TextureLoader();
    textureLoader.load('./img/earth.png',function(texture){
        earth = new THREE.Mesh(
            new THREE.SphereBufferGeometry(1.5,30,30),
            new THREE.MeshLambertMaterial({
                map: texture
            })
        );
        scene.add(earth);
        nextFunctions.push(function(){
            earth.rotation.y += 0.02;
        })
    });


    let gltfLoader = new GLTFLoader();
    gltfLoader.load('./model/bin.gltf',function(gltf){
        let bin1 = gltf.scene.children[0];
        window.bin1 = bin1;
        bin1.scale.setScalar(.15);
        bin1.rotation.set(0,0,0);
        bin1.position.set(-2,1.5,0);

        let bin2 = bin1.clone();
        bin2.children[0].material = bin2.children[0].material.clone();
        bin2.children[0].material.color.set(0xcc2222);
        bin2.position.x += 1.333;

        let bin3 = bin2.clone();
        bin3.children[0].material = bin3.children[0].material.clone();
        bin3.children[0].material.color.set(0xcccc22);
        bin3.position.x += 1.333;
        let bin4 = bin3.clone();
        bin4.children[0].material = bin4.children[0].material.clone();
        bin4.children[0].material.color.set(0x3333cc);
        bin4.position.x += 1.333;

        bins = new THREE.Group();
        bins.add(bin1,bin2,bin3,bin4);
        scene.add(bins);

        window.bins = bins;


    });

    let rubbish1 = new THREE.Mesh(
        new THREE.BoxBufferGeometry(.5,.5,.5),
        new THREE.MeshLambertMaterial({
            transparent:true, 
            depthFunc: THREE.AlwaysDepth,
            color: 0x222222
        })
    );
    rubbish1.position.set(-2.5,-2,0);
    let rubbish2 = rubbish1.clone();
    rubbish2.position.x += 1;
    let rubbish3 = rubbish2.clone();
    rubbish3.position.x += 1;
    let rubbish4 = rubbish3.clone();
    rubbish4.position.x += 1;
    let rubbish5 = rubbish4.clone();
    rubbish5.position.x += 1;
    let rubbish6 = rubbish5.clone();
    rubbish6.position.x += 1;
    rubbishs = new THREE.Group();
    rubbishs.add(rubbish1,rubbish2,rubbish3,rubbish4,rubbish5,rubbish6)
    scene.add(rubbishs);

    plane = new THREE.Mesh(
        new THREE.PlaneBufferGeometry(60,60),
        new THREE.MeshBasicMaterial({opacity:0,transparent:true})
    );
    scene.add(plane);

    let light = new THREE.AmbientLight(0xffffff,.5);
    scene.add(light);

    let light2 = new THREE.DirectionalLight(0xffffff,.7);
    let lightTarget = new THREE.Object3D();
    lightTarget.position.set(1,-1,-1);
    light2.target=lightTarget;
    scene.add(lightTarget);
    scene.add(light2);

}

function createRay(){
    let raycaster = new THREE.Raycaster();

    function getMousePos(e){ // 发生射线需要的位置, e为鼠标事件
        let mousePos = new THREE.Vector3();
        let rendererSize=renderer.getSize();
        mousePos.set(e.offsetX/rendererSize.x-.5, -(e.offsetY/rendererSize.y-.5));
        mousePos.x *= 2;
        mousePos.y *= 2;
        return mousePos;
    }
    
    renderer.domElement.addEventListener(`mousedown` , function(e){
        if(e.button != 0) return; 
        rayLaunch(e);

        function rayLaunch(e){
            let mousePos = getMousePos(e);
            raycaster.setFromCamera(mousePos, camera);

            let intersection = raycaster.intersectObjects([...rubbishs.children]);
            
            if(intersection.length){

                selectedRubbish.rubbish = intersection[0].object;
                selectedRubbish.pos.copy(selectedRubbish.rubbish.position);
                console.log(`intersection`,intersection);
            }
        }
    });

    renderer.domElement.addEventListener(`mouseup` , function(e){
        if(e.button != 0) return; // 如果不是左击, 直接跳出
        if(selectedRubbish.rubbish == null) return;

        rayLaunch(e);

        function rayLaunch(e){
            let mousePos = getMousePos(e);
            let items = []; // 可以点击/受射线影响的对象
            for(let i = 0; i<bins.children.length; i++){
                items.push(...bins.children[i].children);
            }
            raycaster.setFromCamera(mousePos, camera);

            console.log(`items`,items);
            let intersection = raycaster.intersectObjects(items)


            if(intersection.length){
                selectedRubbish.rubbish.parent.remove(selectedRubbish.rubbish);
            }else{
                selectedRubbish.rubbish.position.copy(selectedRubbish.pos);
                selectedRubbish.rubbish = null;
            }
        }

    });

    renderer.domElement.addEventListener(`mousemove` , function(e){
        if(selectedRubbish.rubbish == null)
            return;
        
        rayLaunch(e);
        function rayLaunch(e){
            let mousePos = getMousePos(e);
            raycaster.setFromCamera(mousePos, camera);
            let intersection = raycaster.intersectObjects([plane]);

            if(intersection.length){
                selectedRubbish.rubbish.position.copy(intersection[0].point);
            }
        }
    });

}